﻿using Abp.Configuration.Startup;
using Abp.Dependency;
using Abp.Json;
using Abp.MultiTenancy;
using Abp.Runtime.Session;
using Abp.Web.Configuration;
using Mt.Site.Core.Organizations.UserCache;
using System.Text;

namespace Mt.Site.Core.Configuration
{
    //TODO: 给GetScript 用的，随着angularjs后台的停用，这个也弃用的， 待删
    public class OaCustomConfigScriptManager : ICustomConfigScriptManager, ITransientDependency
    {
        private readonly IUserAndUnitFinder _userAndUnitFinder;
        private readonly IAbpStartupConfiguration _abpStartupConfiguration;

        public IAbpSession AbpSession { get; set; }

        private readonly ITenantStore _tenantStore;


        public OaCustomConfigScriptManager(
            ITenantStore tenantStore,
            IAbpStartupConfiguration abpStartupConfiguration,
            IUserAndUnitFinder userAndUnitFinder)
        {
            _tenantStore = tenantStore;
            _abpStartupConfiguration = abpStartupConfiguration;
            _userAndUnitFinder = userAndUnitFinder;

            AbpSession = NullAbpSession.Instance;
        }

        public string GetScript()
        {
            var script = new StringBuilder();

            script.AppendLine("(function(abp){");
            script.AppendLine();

            script.AppendLine("    abp.custom = " + _abpStartupConfiguration.GetCustomConfig().ToJsonString(camelCase: true, indented: true));

            var userInfo = _userAndUnitFinder.GetCurrentUserInfo();
            if (userInfo != null)
            {
                script.AppendLine("    abp.oaUser = " + _userAndUnitFinder.GetCurrentUserInfo().ToJsonString(camelCase: true, indented: true));
            }
            else
            {
                script.AppendLine("    abp.oaUser = null");
            }

            var currentUser = GetCurrentUserInfo();
            if (currentUser != null)
            {
                script.AppendLine("    abp.currentUser = " + currentUser.ToJsonString(camelCase: true, indented: true));
            }
            else
            {
                script.AppendLine("    abp.currentUser = null");
            }

            script.AppendLine();
            script.Append("})(abp);");

            return script.ToString();
        }

        private CurrentUserInfo GetCurrentUserInfo()
        {
            if (AbpSession.ImpersonatorUserId.HasValue)
            {
                var info = _userAndUnitFinder.GetUserInfo(AbpSession.ImpersonatorTenantId, AbpSession.ImpersonatorUserId.Value);
                if (info == null)
                {
                    return null;
                }

                var tenantName = AbpSession.ImpersonatorTenantId.HasValue ?
                    _tenantStore.Find(AbpSession.ImpersonatorTenantId.Value).TenancyName : null;

                return new CurrentUserInfo
                {
                    IsImpersonator = true,
                    TenantId = AbpSession.ImpersonatorTenantId,
                    UserId = AbpSession.ImpersonatorUserId.Value,
                    TenantName = tenantName,
                    UserName = info.UserName,
                    SurName = info.Surname,
                    LoginName = info.LoginName
                };
            }
            else if (AbpSession.UserId.HasValue)
            {
                var info = _userAndUnitFinder.GetUserInfo(AbpSession.TenantId, AbpSession.UserId.Value);
                if (info == null)
                {
                    return null;
                }

                var tenantName = AbpSession.TenantId.HasValue ?
                    _tenantStore.Find(AbpSession.TenantId.Value).TenancyName : null;

                return new CurrentUserInfo
                {
                    IsImpersonator = false,
                    TenantId = AbpSession.TenantId,
                    UserId = AbpSession.UserId.Value,
                    TenantName = tenantName,
                    UserName = info.UserName,
                    SurName = info.Surname,
                    LoginName = info.LoginName
                };
            }
            else
            {
                return null;
            }
        }
    }
}
